package cn.yangliu.nacos.management.web.oauth2;

import java.util.Optional;

import cn.yangliu.jpa.handler.JpaHandler;
import cn.yangliu.nacos.comm.config.security.annotations.Authorize;
import cn.yangliu.nacos.comm.model.Oauth2InsertModel;
import cn.yangliu.nacos.comm.model.Oauth2Token;
import cn.yangliu.nacos.comm.model.Oauth2UpdateOtherModel;
import cn.yangliu.nacos.comm.model.Oauth2UpdateOtherPasswordModel;
import cn.yangliu.nacos.comm.model.Oauth2UserModel;
import cn.yangliu.nacos.comm.oauth.TokenHandler;
import cn.yangliu.nacos.comm.tools.SecurityUtils;
import cn.yangliu.nacos.management.entity.oauth2.Oauth2User;
import cn.yangliu.nacos.management.model.Oauth2UserQueryModel;
import cn.yangliu.nacos.management.service.oauth2.Oauth2UserService;
import cn.yangliu.operation.annotation.Action;
import cn.yangliu.operation.annotation.Module;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * The type of nacos.
 *
 * @author 问道于盲
 * @date 2020 -01-01
 */
@RequestMapping("/user")
@RestController
@Api(value = "用户管理", tags = "用户管理")
@Module("oauth2管理-用户管理")
public class Oauth2UserController {

    /**
     * current class instance's member.
     * The User service.
     */
    @Autowired
    private Oauth2UserService userService;

    /**
     * current class instance's member.
     * The Token handler.
     */
    @Autowired
    private TokenHandler tokenHandler;

    /**
     * current class instance's member.
     * The Jpa handler.
     */
    private JpaHandler jpaHandler = JpaHandler.INSTANCE;

    /**
     * Insert oauth 2 user model.
     *
     * @param model the model
     * @return the oauth 2 user model
     */
    @PostMapping
    @ApiOperation("新增用户")
    @Authorize("oauth2user:insert")
    @Action("新增用户")
    public Oauth2UserModel insert(@RequestBody @Validated Oauth2InsertModel model) {
        Oauth2UserModel currentUser = SecurityUtils.getCurrentUser();
        Oauth2Token token = tokenHandler.load(currentUser.getUsername());
        return userService.insert(model, token.getAccessToken());
    }

    /**
     * Update oauth 2 user model.
     *
     * @param model the model
     * @return the oauth 2 user model
     */
    @PutMapping
    @ApiOperation("修改用户")
    @Authorize("oauth2user:update")
    @Action("修改用户")
    public Oauth2UserModel update(@RequestBody @Validated Oauth2UpdateOtherModel model) {
        Oauth2UserModel currentUser = SecurityUtils.getCurrentUser();
        Oauth2Token token = tokenHandler.load(currentUser.getUsername());
        return userService.update(model, token.getAccessToken());
    }

    /**
     * Update.
     *
     * @param id the id
     */
    @DeleteMapping("/{id}")
    @ApiOperation("删除用户")
    @Authorize("oauth2user:delete")
    @Action("删除用户")
    public void update(@PathVariable("id") Long id) {
        userService.deleteById(id);
    }

    /**
     * Find one oauth 2 user.
     *
     * @param id the id
     * @return the oauth 2 user
     */
    @GetMapping("/{id}")
    @ApiOperation("根据id查询用户")
    @Authorize("oauth2user:query")
    public Oauth2User findOne(@PathVariable("id") Long id) {
        Optional<Oauth2User> optional = userService.findById(id);
        return optional.orElse(null);
    }

    /**
     * Page page.
     *
     * @param model the model
     * @return the page
     */
    @GetMapping("/page")
    @ApiOperation("分页查询用户")
    @Authorize("oauth2user:query")
    public Page<Oauth2User> page(@Validated Oauth2UserQueryModel model) {
        Specification<Oauth2User> specification = jpaHandler.buildSpecification(model);
        return userService.findAll(specification, model.build());
    }

    /**
     * Password boolean.
     *
     * @param model the model
     * @return the boolean
     */
    @PutMapping("/password")
    @ApiOperation("重置密码")
    @Authorize("oauth2user:reset")
    public boolean password(@RequestBody @Validated Oauth2UpdateOtherPasswordModel model) {
        Oauth2UserModel currentUser = SecurityUtils.getCurrentUser();
        String username = currentUser.getUsername();
        Oauth2Token oauth2Token = tokenHandler.load(username);
        return userService.updatePassword(model, oauth2Token.getAccessToken());
    }
}
